﻿using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Spine.Unity;
using System.IO;
using System;

public class SpineCreateControl : MonoSingleton<SpineCreateControl>
{
    public Action<SkeletonAnimation> onSkelAnimCreate;

    public Material materialPropertySource;
    Spine.ExposedList<Spine.Animation> anims;
    Spine.ExposedList<Spine.Skin> skins;
    SkeletonAnimation spineAnimation;
    int animIndex = 0;
    int skinIndex = 0;

    private void Start() {
        // LoadTheSpine("D:/Git/rightdown-popup/Assets/StreamingAssets/packages/test1/assets/Event_14/Event_14.json");
    }

    public void LoadTheSpine(string jsonFilePath)
    {
        if(spineAnimation != null)
        {
            Destroy(spineAnimation.gameObject);
        }

        if (!string.IsNullOrEmpty(jsonFilePath))
        {

            string folderName = Path.GetDirectoryName(jsonFilePath);
            string spinePrefix = Path.GetFileNameWithoutExtension(jsonFilePath);
            string spineBasePath = Path.Combine(folderName, spinePrefix);

            string texturePath = string.Format("{0}.png", spineBasePath);

            if (File.Exists(texturePath))
            {
                StartCoroutine(Res.LoadExternalTexture(texturePath, (tex) =>
                {
                    var atlasText = new TextAsset(File.ReadAllText(spineBasePath + ".atlas"));

                    tex.name = spinePrefix;
                    Texture2D[] textures = new Texture2D[] { tex };
                    var skeletonJson = new TextAsset(File.ReadAllText(jsonFilePath));
                    var runtimeSAA = SpineAtlasAsset.CreateRuntimeInstance(atlasText, textures, materialPropertySource, true);
                    var runtimeSDA = SkeletonDataAsset.CreateRuntimeInstance(skeletonJson, runtimeSAA, true);

                    runtimeSDA.GetSkeletonData(false); //预加载
                    runtimeSDA.name = skeletonJson.name + "_SkeletonData";
                    spineAnimation = SkeletonAnimation.NewSkeletonAnimationGameObject(runtimeSDA);  //初始化游戏对象
                    spineAnimation.loop = true;
                    spineAnimation.transform.SetParent(transform);

                    anims = spineAnimation.skeletonDataAsset.GetSkeletonData(true).Animations;
                    skins = spineAnimation.skeleton.Data.Skins;

                    string animName = anims.Items[0].Name;
                    spineAnimation.AnimationName = animName;

                    spineAnimation.transform.localPosition = transform.position;
                    spineAnimation.transform.SetParent(this.transform, false);

                    spineAnimation.transform.gameObject.name = runtimeSDA.name.ToString();

                    FixScale();

                    if(onSkelAnimCreate != null) onSkelAnimCreate(spineAnimation);

                }));
            }
        }
    }

    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Alpha0))
        {
            animIndex++;
            if (animIndex >= anims.Items.Length)
                animIndex = 0;

            string animName = anims.Items[animIndex].Name;
            spineAnimation.AnimationName = animName;
        }

        if (Input.GetKeyDown(KeyCode.Alpha9))
        {
            animIndex--;
            if (animIndex < 0)
                animIndex = anims.Items.Length;

            string animName = anims.Items[animIndex].Name;
            spineAnimation.AnimationName = animName;
        }

        if (Input.GetKeyDown(KeyCode.X))
        {
            transform.localScale = new Vector3(transform.localScale.x * -1, transform.localScale.y, transform.localScale.z);
        }

        if (Input.GetKeyDown(KeyCode.C))
        {
            if (skins.Count > 1)
            {
                print(skinIndex);
                string skinName = skins.Items[skinIndex].Name;
                spineAnimation.skeleton.SetSkin(skinName);
                spineAnimation.skeleton.SetSlotsToSetupPose();
                spineAnimation.AnimationState.Apply(spineAnimation.skeleton);

                skinIndex++;
                if (skinIndex >= skins.Items.Length)
                    skinIndex = 0;
            }
        }
    }

    void FixScale()
    {
        MeshRenderer renderer = spineAnimation.GetComponent<MeshRenderer>();
        Vector3 rightTop = renderer.bounds.center + renderer.bounds.extents;
        Vector3 leftDown = renderer.bounds.center - renderer.bounds.extents;
        Vector3 vrt = Camera.main.WorldToViewportPoint(rightTop);
        Vector3 vld = Camera.main.WorldToViewportPoint(leftDown);
        float radio = 1f / Mathf.Abs(vrt.y - vld.y);
        spineAnimation.transform.localScale = radio * Vector3.one;
        spineAnimation.transform.position -= renderer.bounds.center - transform.position;
    }
}
